#include "event/EventManager.hpp"
#include <iostream>
#include <chrono>

namespace WaveGuard {

    /**
     * @brief 事件管理器构造函数
     * @details 初始化事件管理器的成员变量，接收一个线程池实例
     */
    EventManager::EventManager(std::shared_ptr<ThreadPool> threadPool)
        : m_threadPool(threadPool), m_maxProcessTimeMs(100) {
        // 验证线程池有效性
        if (!m_threadPool) {
            throw std::invalid_argument("ThreadPool cannot be null");
        }
    }

    /**
     * @brief 事件管理器析构函数
     * @details 确保资源正确释放
     */
    EventManager::~EventManager() {
        // 清空事件队列
        std::lock_guard<std::mutex> lock(m_mutex);
        decltype(m_eventQueue) emptyQueue;
        std::swap(m_eventQueue, emptyQueue);
    }

    /**
     * @brief 注册事件监听器
     * @param type 要监听的事件类型
     * @param listener 事件监听器
     * @details 将指定的监听器添加到对应事件类型的监听器列表中，使用互斥锁保证线程安全。
     */
    void EventManager::subscribe(EventType type, std::shared_ptr<EventListener> listener) {
        std::lock_guard<std::mutex> lock(m_mutex);
        m_listeners[type].push_back(listener);
    }

    /**
     * @brief 取消注册事件监听器
     * @param type 要取消监听的事件类型
     * @param listener 事件监听器
     * @details 从指定事件类型的监听器列表中移除该监听器，使用互斥锁保证线程安全。
     */
    void EventManager::unsubscribe(EventType type, std::shared_ptr<EventListener> listener) {
        std::lock_guard<std::mutex> lock(m_mutex);

        // 查找指定事件类型的监听器列表
        auto it = m_listeners.find(type);
        if (it != m_listeners.end()) {
            auto &listeners = it->second;
            listeners.erase(
                std::remove_if(listeners.begin(), listeners.end(),
                    [&listener](const std::shared_ptr<EventListener> &l) {
                        return l == listener;
                    }),
                listeners.end()
            );
        }
    }

    /**
     * @brief 同步发布事件（立即处理）
     * @param event 要发布的事件
     * @details 将事件直接分发给所有注册的监听器进行处理，调用 processEvent 方法。
     */
    void EventManager::publish(const std::shared_ptr<Event> &event) {
        processEvent(event);
    }

    /**
     * @brief 异步发布事件（放入队列稍后处理）
     * @param event 要发布的事件
     * @details  将事件添加到事件队列中，然后提交一个任务到线程池进行处理
     */
    void EventManager::publishAsync(const std::shared_ptr<Event> &event) {
        m_threadPool->enqueue([this, event]() {
            eventProcessingTask(event);
            });
    }

    /**
     * @brief 处理事件队列中的所有事件
     * @details 记录事件处理开始时间，将全局事件队列中的事件转移到本地队列中，依次处理本地队列中的事件，
     *          处理过程中检查是否超过最大处理时间，若超过则停止处理，将未处理的事件放回全局队列。
     */
    void EventManager::processEvents() {
        auto startTime = std::chrono::steady_clock::now();

        std::queue<std::shared_ptr<Event>> localQueue;

        {
            std::lock_guard<std::mutex> lock(m_mutex);
            localQueue.swap(m_eventQueue);
        }

        while (!localQueue.empty()) {
            auto event = localQueue.front();
            localQueue.pop();

            processEvent(event); // 处理事件事务

            // 检查是否超过最大处理时间
            auto currentTime = std::chrono::steady_clock::now();
            auto elapsedTime = std::chrono::duration_cast<std::chrono::milliseconds>(
                currentTime - startTime).count();

            if (elapsedTime >= m_maxProcessTimeMs) {
                break;
            }
        }

        // 将未处理的事件放回队列
        {
            std::lock_guard<std::mutex> lock(m_mutex);
            while (!localQueue.empty()) {
                m_eventQueue.push(localQueue.front());
                localQueue.pop();
            }
        }
    }

    /**
     * @brief 设置事件处理的最大时间
     * @param ms 最大时间（毫秒）
     */
    void EventManager::setMaxProcessTimeMs(size_t ms) {
        m_maxProcessTimeMs = ms;
    }

    /**
     * @brief 处理单个事件
     * @param event 要处理的事件
     * @details 查找该事件类型的所有监听器，以及类型为 UNKNOWN 的监听器，将事件分发给这些监听器处理，
     *          若处理过程中抛出异常，则捕获并输出错误信息。
     */
    void EventManager::processEvent(const std::shared_ptr<Event> &event) {
        std::vector<std::shared_ptr<EventListener>> listeners;

        {
            std::lock_guard<std::mutex> lock(m_mutex);
            auto it = m_listeners.find(event->getType());
            if (it != m_listeners.end()) {
                listeners = it->second;
            }

            // 处理所有类型的监听器
            it = m_listeners.find(EventType::UNKNOWN);
            if (it != m_listeners.end()) {
                listeners.insert(listeners.end(), it->second.begin(), it->second.end());
            }
        }

        for (const auto &listener : listeners) {
            if (listener) {
                try {
                    listener->onEvent(event);
                } catch (const std::exception &e) {
                    std::cerr << "Exception in event handler: " << e.what() << std::endl;
                }
            }
        }
    }

    /**
     * @brief 事件处理任务
     * @param event 要处理的事件
     * @details 在线程池中执行的事件处理任务，包含了超时控制逻辑
     */
    void EventManager::eventProcessingTask(const std::shared_ptr<Event> &event) {
        auto startTime = std::chrono::steady_clock::now();

        processEvent(event);

        // 检查处理时间
        auto currentTime = std::chrono::steady_clock::now();
        auto elapsedTime = std::chrono::duration_cast<std::chrono::milliseconds>(
            currentTime - startTime).count();

        if (elapsedTime > m_maxProcessTimeMs) {
            std::cerr << "Event processing exceeded maximum time: "
                << elapsedTime << "ms (max " << m_maxProcessTimeMs << "ms)" << std::endl;
        }
    }

} // namespace WaveGuard
